/*
 * Exploder
 * 
 * Tero Pyylampi (218437), Jussi Tuurinkoski (211594)
 *
 * Interface for handling with Lua
 */


#include "LuaInterface.h"
#include "Common.h"
#include "game/misc/GameLevelEngine.h"

extern "C" {
	#include "lua.h"
	#include "lualib.h"
	#include "lauxlib.h"
}

using namespace cocos2d;

// static functions available for lua scripts

// create new construction element
static int createConstructionElement( lua_State *L ) {
	GameLevelEngine::createConstructionElement(
			static_cast< ElementType >( lua_tointeger( L, 1 ) ),
			lua_tonumber( L, 2 ), 
			lua_tonumber( L, 3 ), 
			lua_tonumber( L, 4 ),
			static_cast< PhysicObjectItems >( lua_tointeger( L, 5 ) )
		);
	return 0;
};

// default constructor
LuaInterface::LuaInterface() {
	// initialize lua interface
	initEngine();
}

// default destructor
LuaInterface::~LuaInterface() {}

// initialize engine
void LuaInterface::initEngine() {
	// initialize lua-engine
	mLuaEngine = CCLuaEngine::engine();
	CCScriptEngineManager::sharedManager()->setScriptEngine( mLuaEngine );

	// register functions
	lua_State *L = mLuaEngine->getLuaState();
	lua_register( L, "createConstructionElement", createConstructionElement );
}

// call init function of the script
void LuaInterface::callInitFunction() {
	lua_State *L = mLuaEngine->getLuaState();
	lua_getglobal( L, "init" );
	lua_call( L, 0, 0 );
}

// call main update function of the script
void LuaInterface::callUpdateFunction( cocos2d::ccTime dt ) {
	lua_State *L = mLuaEngine->getLuaState();
	lua_getglobal( L, "update" );
	lua_pushnumber( L, static_cast< float >( dt ) );
	lua_call( L, 1, 0 );
}

// get lua engine
cocos2d::CCScriptEngineProtocol *LuaInterface::getEngine() {
	return mLuaEngine;
}

// execute script
void LuaInterface::executeScript( const char *script ) {
	#if ( CC_TARGET_PLATFORM == CC_PLATFORM_ANDROID )
		unsigned long size;
		char *pFileContent = ( char* )CCFileUtils::getFileData( script, "r", &size );

		if ( pFileContent ) {
			char *pCodes = new char[ size + 1 ];
			pCodes[size] = '\0';
			memcpy( pCodes, pFileContent, size );
			delete[] pFileContent;

			mLuaEngine->executeString( pCodes );
			delete[] pCodes;
		}
	#else
		string path = CCFileUtils::fullPathFromRelativePath( script );
		mLuaEngine->addSearchPath( path.substr( 0, path.find_last_of( "/" ) ).c_str() );
		mLuaEngine->executeScriptFile( path.c_str() );
	#endif 
}
